package top.zywork.controller;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.validation.BindingResult;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import top.zywork.annotation.ContentSecCheck;
import top.zywork.annotation.SysLog;
import top.zywork.common.BeanUtils;
import top.zywork.common.BindingResultUtils;
import top.zywork.constant.CommonConstant;
import top.zywork.constant.ShippingAddressConstant;
import top.zywork.dos.SchoolDO;
import top.zywork.dos.ShippingAddressDO;
import top.zywork.dto.PagerDTO;
import top.zywork.dto.ShippingAddressDTO;
import top.zywork.query.ShippingAddressQuery;
import top.zywork.query.wx.ShippingAddressWxQuery;
import top.zywork.wx.save.ShippingAddressSave;
import top.zywork.security.SecurityUtils;
import top.zywork.service.SchoolService;
import top.zywork.service.ShippingAddressService;
import top.zywork.service.impl.ShippingAddressExServiceImpl;
import top.zywork.vo.ResponseStatusVO;
import top.zywork.vo.PagerVO;
import top.zywork.vo.ShippingAddressVO;
import top.zywork.vo.wx.DefaultShippingAddressWxVO;
import top.zywork.vo.wx.ShippingAddressWxVO;

import java.util.List;
import java.util.stream.Collectors;

/**
 * 微信小程序端地址控制器类<br/>
 *
 * 创建于2019-06-27<br/>
 *
 * @author http://zywork.top 王振宇 Animo
 * @version 1.0
 */
@RestController
@RequestMapping("/shipping-address")
@Slf4j
public class ShippingAddressController extends BaseController {

    private ShippingAddressService shippingAddressService;

    @Autowired
    private ShippingAddressExServiceImpl shippingAddressExService;

    @Autowired
    private SchoolService schoolService;

    @Autowired
    public void setShippingAddressService(ShippingAddressService shippingAddressService) {
        this.shippingAddressService = shippingAddressService;
    }

    /**
     * 用户保存收货地址 postman TODO 后期需要加入一些校验
     * @param bindingResult
     * @return
     */
    @PostMapping("user/save")
    @SysLog(description = "用户保存收货地址")
    @ContentSecCheck
    public ResponseStatusVO userSave(@RequestBody @Validated ShippingAddressSave shippingAddressSave, BindingResult bindingResult) {
        shippingAddressSave.setUserId(SecurityUtils.getJwtUser().getUserId());
        return save(shippingAddressSave, bindingResult);
    }
    /**
     * 用户删除收货地址 postman
     * @param id
     * @return
     */
    @GetMapping("user/remove/{id}")
    @SysLog(description = "用户删除收货地址")
    public ResponseStatusVO userRemoveById(@PathVariable("id") Long id) {
        if (hasShippingAddress(id, SecurityUtils.getJwtUser().getUserId())) {
            return removeById(id);
        } else {
            return ResponseStatusVO.dataError("不存在的用户地址编号", null);
        }
    }
    /**
     * 用户更新收货地址 postman TODO 后期需要加入一些校验
     * @param bindingResult
     * @return
     */
    @PostMapping("user/update")
    @SysLog(description = "用户更新收货地址")
    public ResponseStatusVO userUpdate(@RequestBody @Validated ShippingAddressVO shippingAddressVO, BindingResult bindingResult) {
        if (bindingResult.hasErrors()) {
            return ResponseStatusVO.dataError(BindingResultUtils.errorString(bindingResult), null);
        }
        if (!hasShippingAddress(shippingAddressVO.getId(), SecurityUtils.getJwtUser().getUserId())) {
            return ResponseStatusVO.dataError("不正确的用户地址编号", null);
        }
        return update(shippingAddressVO);
    }

    /**
     * 用户更新收货地址 postman
     * @param shippingAddressVO
     * @return
     */
    @PostMapping("user/is-default")
    @SysLog(description = "用户更新默认收货状态")
    public ResponseStatusVO isDefault(@RequestBody ShippingAddressVO shippingAddressVO) {
        shippingAddressVO.setUserId(SecurityUtils.getJwtUser().getUserId());
        if (!hasShippingAddress(shippingAddressVO.getId(), SecurityUtils.getJwtUser().getUserId())) {
            return ResponseStatusVO.dataError("不正确的用户地址编号", null);
        }
        return update(shippingAddressVO);
    }

    /**
     * 根据条件查询用户的收货地址
     *
     * @param shippingAddressWxQuery
     * @return
     */
    @PostMapping("user/pager-cond")
    public ResponseStatusVO userListPageByCondition(@RequestBody ShippingAddressWxQuery shippingAddressWxQuery) {

        shippingAddressWxQuery.setUserId(SecurityUtils.getJwtUser().getUserId());

        List<ShippingAddressDO> list = shippingAddressExService.list(new QueryWrapper<ShippingAddressDO>().eq("user_id", shippingAddressWxQuery.getUserId())
                .eq("is_active", CommonConstant.IS_ACTIVE_TRUE)
                .like(StringUtils.isNotEmpty(shippingAddressWxQuery.getPhoneOrName()), "real_name", shippingAddressWxQuery.getPhoneOrName()).or()
                .like(StringUtils.isNotEmpty(shippingAddressWxQuery.getPhoneOrName()), "phone", shippingAddressWxQuery.getPhoneOrName()));
        List<ShippingAddressWxVO> wxVOS;
        wxVOS = list.stream().map(e->{
            ShippingAddressWxVO shippingAddressWxVO = new ShippingAddressWxVO();
            shippingAddressWxVO.setCombination(e.getSchool() + e.getStoriedBuilding() + e.getArea());
            BeanUtils.copy(e,shippingAddressWxVO);
            return shippingAddressWxVO;
        }).collect(Collectors.toList());

        return ResponseStatusVO.ok("查询成功", wxVOS);
    }

    /**
     * 查询当前用户的默认地址
     * @return
     */
    @PostMapping("user/default-address")
    public ResponseStatusVO defaultAddress() {
        long userId = SecurityUtils.getJwtUser().getUserId();
        // 通过用户ID查询默认地址
        ShippingAddressDO result = shippingAddressExService.getOne(new QueryWrapper<ShippingAddressDO>().eq("user_id", userId)
                .eq("is_active", CommonConstant.IS_ACTIVE_TRUE)
                .eq("is_default", ShippingAddressConstant.IS_DEFAULT_TRUE));

        DefaultShippingAddressWxVO defaultShippingAddressWxVO = new DefaultShippingAddressWxVO();

        ShippingAddressWxVO shippingAddressWxVO = new ShippingAddressWxVO();
        if(result!=null){
            defaultShippingAddressWxVO.setFlag(Boolean.TRUE);
            org.springframework.beans.BeanUtils.copyProperties(result,shippingAddressWxVO);
        }else{
            defaultShippingAddressWxVO.setFlag(Boolean.FALSE);
        }
        shippingAddressWxVO.setCombination(result.getSchool() + result.getStoriedBuilding() + result.getArea());
        defaultShippingAddressWxVO.setShippingAddressWxVO(shippingAddressWxVO);
        return ResponseStatusVO.ok("查询成功", defaultShippingAddressWxVO);
    }

    @PostMapping("user/one-address/{id}")
    public ResponseStatusVO oneAddress(@PathVariable("id") Long id){
        long userId = SecurityUtils.getJwtUser().getUserId();
        ShippingAddressDO one = shippingAddressExService.getOne(new QueryWrapper<ShippingAddressDO>()
                .eq("is_active", CommonConstant.IS_ACTIVE_TRUE)
                .eq("user_id", userId)
                .eq("id", id));
        ShippingAddressWxVO copy = BeanUtils.copy(one, ShippingAddressWxVO.class);
        return ResponseStatusVO.ok("查询成功", copy);
    }

    @PostMapping("admin/save")
    @SysLog(description = "后台保存ShippingAddressVO")
    public ResponseStatusVO save(@RequestBody @Validated ShippingAddressSave shippingAddressSave, BindingResult bindingResult) {
        if (bindingResult.hasErrors()) {
            return ResponseStatusVO.dataError(BindingResultUtils.errorString(bindingResult), null);
        }
        // 校验学校ID是否存在
        SchoolDO schoolDO = schoolService.checkSchool(shippingAddressSave.getSchoolId());
        if(schoolDO == null){
            return ResponseStatusVO.error("学校不存在",null);
        }
        shippingAddressSave.setSchool(schoolDO.getSchool());
        shippingAddressService.saveAddress(BeanUtils.copy(shippingAddressSave, ShippingAddressDTO.class));
        return ResponseStatusVO.ok("添加成功", null);
    }

    @PostMapping("admin/batch-save")
    @SysLog(description = "后台批量保存ShippingAddressVO")
    public ResponseStatusVO saveBatch(@RequestBody @Validated List<ShippingAddressVO> shippingAddressVOList, BindingResult bindingResult) {
        if (bindingResult.hasErrors()) {
            return ResponseStatusVO.dataError(BindingResultUtils.errorString(bindingResult), null);
        }
        shippingAddressService.saveBatch(BeanUtils.copyListObj(shippingAddressVOList, ShippingAddressDTO.class));
        return ResponseStatusVO.ok("批量添加成功", null);
    }

    @GetMapping("admin/remove/{id}")
    @SysLog(description = "后台删除ShippingAddressVO")
    public ResponseStatusVO removeById(@PathVariable("id") Long id) {
        shippingAddressService.removeById(id);
        return ResponseStatusVO.ok("删除成功", null);
    }

    @PostMapping("admin/batch-remove")
    @SysLog(description = "后台批量删除ShippingAddressVO")
    public ResponseStatusVO removeByIds(@RequestBody String[] ids) {
        shippingAddressService.removeByIds(top.zywork.common.StringUtils.strArrayToLongArray(ids));
        return ResponseStatusVO.ok("批量删除成功", null);
    }

    @PostMapping("admin/update")
    @SysLog(description = "后台更新ShippingAddressVO")
    public ResponseStatusVO update(@RequestBody @Validated ShippingAddressVO shippingAddressVO, BindingResult bindingResult) {
        if (bindingResult.hasErrors()) {
            return ResponseStatusVO.dataError(BindingResultUtils.errorString(bindingResult), null);
        }
        int updateRow = shippingAddressService.update(BeanUtils.copy(shippingAddressVO, ShippingAddressDTO.class));
        return updateRow == 1 ? ResponseStatusVO.ok("更新成功", null)
                : ResponseStatusVO.dataError("未更新成功，数据版本号错误或不满足更新的条件", null);
    }


    private ResponseStatusVO update(ShippingAddressVO shippingAddressVO) {
        int updateRows = shippingAddressService.updateAddress(BeanUtils.copy(shippingAddressVO, ShippingAddressDTO.class));
        if (updateRows == 1) {
            return ResponseStatusVO.ok("更新成功", null);
        } else {
            return ResponseStatusVO.dataError("数据版本号有问题，在此更新前数据已被更新", null);
        }
    }

    @PostMapping("admin/batch-update")
    @SysLog(description = "后台批量更新ShippingAddressVO")
    public ResponseStatusVO updateBatch(@RequestBody @Validated List<ShippingAddressVO> shippingAddressVOList, BindingResult bindingResult) {
        if (bindingResult.hasErrors()) {
            return ResponseStatusVO.dataError(BindingResultUtils.errorString(bindingResult), null);
        }
        shippingAddressService.updateBatch(BeanUtils.copyListObj(shippingAddressVOList, ShippingAddressDTO.class));
        return ResponseStatusVO.ok("批量更新成功", null);
    }

    @PostMapping("admin/active")
    @SysLog(description = "后台激活或冻结ShippingAddressVO")
    public ResponseStatusVO active(@RequestBody ShippingAddressVO shippingAddressVO) {
        shippingAddressService.update(BeanUtils.copy(shippingAddressVO, ShippingAddressDTO.class));
        return ResponseStatusVO.ok("激活或冻结成功", null);
    }

    @PostMapping("admin/batch-active")
    @SysLog(description = "后台批量激活或冻结ShippingAddressVO")
    public ResponseStatusVO activeBatch(@RequestBody @Validated List<ShippingAddressVO> shippingAddressVOList) {
        shippingAddressService.updateBatch(BeanUtils.copyListObj(shippingAddressVOList, ShippingAddressDTO.class));
        return ResponseStatusVO.ok("批量激活或冻结成功", null);
    }

    @GetMapping("admin/one/{id}")
    public ResponseStatusVO getById(@PathVariable("id") Long id) {
        ShippingAddressVO shippingAddressVO = new ShippingAddressVO();
        Object obj = shippingAddressService.getById(id);
        if (obj != null) {
            shippingAddressVO = BeanUtils.copy(obj, ShippingAddressVO.class);
        }
        return ResponseStatusVO.ok("查询成功", shippingAddressVO);
    }

    @GetMapping("admin/all")
    public ResponseStatusVO listAll() {
        PagerDTO pagerDTO = shippingAddressService.listAll();
        PagerVO pagerVO = BeanUtils.copy(pagerDTO, PagerVO.class);
        pagerVO.setRows(BeanUtils.copyList(pagerDTO.getRows(), ShippingAddressVO.class));
        return ResponseStatusVO.ok("查询成功", pagerVO);
    }

    @PostMapping("admin/all-cond")
    public ResponseStatusVO listAllByCondition(@RequestBody ShippingAddressQuery shippingAddressQuery) {
        PagerDTO pagerDTO = shippingAddressService.listAllByCondition(shippingAddressQuery);
        PagerVO pagerVO = BeanUtils.copy(pagerDTO, PagerVO.class);
        pagerVO.setRows(BeanUtils.copyList(pagerDTO.getRows(), ShippingAddressVO.class));
        return ResponseStatusVO.ok("查询成功", pagerVO);
    }

    @PostMapping("admin/pager-cond")
    public ResponseStatusVO listPageByCondition(@RequestBody ShippingAddressQuery shippingAddressQuery) {
        PagerDTO pagerDTO = shippingAddressService.listPageByCondition(shippingAddressQuery);
        PagerVO pagerVO = BeanUtils.copy(pagerDTO, PagerVO.class);
        pagerVO.setRows(BeanUtils.copyList(pagerDTO.getRows(), ShippingAddressVO.class));
        return ResponseStatusVO.ok("查询成功", pagerVO);
    }

    @PostMapping("user/pager-cond-list")
    public ResponseStatusVO listPageADDress(@RequestBody ShippingAddressQuery shippingAddressQuery) {
        shippingAddressQuery.setUserId(SecurityUtils.getJwtUser().getUserId());
       return listPageByCondition(shippingAddressQuery);
    }


    private boolean hasShippingAddress(Long addressId, Long userId) {
        ShippingAddressQuery shippingAddressQuery = new ShippingAddressQuery();
        shippingAddressQuery.setId(addressId);
        shippingAddressQuery.setUserId(userId);
        return shippingAddressService.countByCondition(shippingAddressQuery) > 0;
    }
}
